CORE-1386: EasyMesh topology DML output is failing when WPA2-Personal is forced with MLO enabled on non-6G vaps#1140
CORE-1386: EasyMesh topology DML output is failing when WPA2-Personal is forced with MLO enabled on non-6G vaps#1140bsomanath wants to merge 12 commits into
Conversation
… in RDK-B Signed-off-by: Somanath Bulusu <bsomanath@plume.com>
… in RDK-B RDKBWIFI-388: Add support for onboarding extender using WPS mechanism in RDK-B
removed unused unistd.h usage Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
…onal on 2.4G & 5G and disabling MLO Signed-off-by: Somanath Bulusu <bsomanath@plume.com>
There was a problem hiding this comment.
Pull request overview
This PR addresses EasyMesh topology DML output failures seen when WPS onboarding is enabled (notably when WPA2-Personal is forced with MLO enabled on non‑6GHz VAPs). It adds WPS support/allowances for mesh extender STA interfaces and introduces a platform-guarded workaround to disable MLO/MLD and force WPA2 settings on private fronthaul VAPs when WPS is enabled.
Changes:
- Relax WPS DML restrictions for mesh STA VAPs when
UWM_EXT_WPS_SUPPORTis enabled (allow WPS configuration/validation paths for STA mesh/extender use-cases). - Add mesh extender WPS onboarding state handling, plus a new HAL callback registration for STA WPS events.
- Add Bananapi R4 +
EM_WPS_FH_HACKlogic to disable MLO/MLD and force WPA2-Personal on 2.4/5GHz private SSIDs when WPS is enabled; additionally adds logic to copy mesh backhaul credentials intomulti_ap_backhaul_*fields.
Reviewed changes
Copilot reviewed 7 out of 7 changed files in this pull request and generated 5 comments.
Show a summary per file
| File | Description |
|---|---|
| source/platform/common/data_model/wifi_dml_cb.c | Allows WPS get/set DML operations for mesh STA when UWM_EXT_WPS_SUPPORT is enabled. |
| source/dml/tr_181/ml/cosa_wifi_dml.c | Adjusts TR-181 WPS handlers/validation to permit extender STA WPS flows under UWM_EXT_WPS_SUPPORT. |
| source/db/wifi_db.c | Adds valid_bh_credentials initialization logic for STA defaults under UWM_EXT_WPS_SUPPORT. |
| source/core/wifi_ctrl.c | Registers a new STA WPS callback and routes WPS STA success into mesh extender service handling. |
| source/core/services/vap_svc.h | Extends mesh extender connection state enum and exposes a WPS credentials received hook under UWM_EXT_WPS_SUPPORT. |
| source/core/services/vap_svc_private.c | Adds Bananapi-specific MLO/MLD disable + WPA2 forcing for private WPS; also copies mesh backhaul credentials into multi_ap_backhaul_*. |
| source/core/services/vap_svc_mesh_ext.c | Adds WPS onboarding states/handling and reinit logic post-credentials for mesh extender STA. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| @@ -1296,6 +1396,7 @@ int vap_svc_mesh_ext_start(vap_svc_t *svc, unsigned int radio_index, wifi_vap_in | |||
| memset(ext, 0, sizeof(vap_svc_ext_t)); | |||
|
|
|||
| ext_set_conn_state(ext, connection_state_disconnected_scan_list_none, __func__, __LINE__); | |||
|
|
|||
| schedule_connect_sm(svc); | |||
|
|
|||
| static void wps_sta_event_callback(unsigned int vap_index, unsigned int event) | ||
| { | ||
| wifi_ctrl_t *ctrl = get_wifictrl_obj(); | ||
| vap_svc_t *ext_svc = NULL; | ||
|
|
||
| wifi_util_info_print(WIFI_CTRL, "%s:%d: WPS STA event callback: vap_index=%d, event=%d\n", | ||
| __func__, __LINE__, vap_index, event); | ||
|
|
||
| /* Only handle WPS_EV_SUCCESS (value 2) */ | ||
| if (event != 2) { | ||
| wifi_util_dbg_print(WIFI_CTRL, "%s:%d: Ignoring non-success WPS event %d\n", | ||
| __func__, __LINE__, event); | ||
| return; | ||
| } | ||
|
|
||
| if (ctrl == NULL) { | ||
| wifi_util_error_print(WIFI_CTRL, "%s:%d: ctrl is NULL\n", | ||
| __func__, __LINE__); | ||
| return; | ||
| } | ||
|
|
||
| /* Find the mesh extender service for this VAP using the existing API */ | ||
| ext_svc = get_svc_by_vap_index(ctrl, vap_index); | ||
| if (ext_svc != NULL && ext_svc->type == vap_svc_type_mesh_ext) { | ||
| /* Found the service - call the WPS credentials handler */ | ||
| wifi_util_info_print(WIFI_CTRL, "%s:%d: Calling vap_svc_mesh_ext_wps_credentials_received " | ||
| "for vap_index %d\n", __func__, __LINE__, vap_index); | ||
| vap_svc_mesh_ext_wps_credentials_received(ext_svc, vap_index); | ||
| } else { | ||
| wifi_util_dbg_print(WIFI_CTRL, "%s:%d: Could not find mesh extender service for vap_index %d " | ||
| "(ext_svc=%p, type=%d)\n", __func__, __LINE__, vap_index, ext_svc, | ||
| ext_svc ? ext_svc->type : -1); | ||
| } |
| // If WPS is enabled on private VAP, copy mesh backhaul credentials into multi_ap_backhaul structure | ||
| if (map->vap_array[i].u.bss_info.wps.enable && isVapPrivate(map->vap_array[i].vap_index)) { | ||
| wifi_vap_name_t vap_names[MAX_NUM_RADIOS] = {0}; | ||
| unsigned int num_vaps = get_list_of_mesh_backhaul(wifi_prop, MAX_NUM_RADIOS, vap_names); | ||
| wifi_vap_info_t *backhaul_vap_info = NULL; | ||
|
|
||
| if (num_vaps > 0) { | ||
| int backhaul_vap_index = convert_vap_name_to_index(wifi_prop, vap_names[0]); | ||
| if (backhaul_vap_index >= 0) { | ||
| backhaul_vap_info = get_wifidb_vap_parameters(backhaul_vap_index); | ||
| } | ||
| } | ||
| if (backhaul_vap_info != NULL && | ||
| strlen((char *)backhaul_vap_info->u.bss_info.ssid) > 0 && | ||
| strlen((char *)backhaul_vap_info->u.bss_info.security.u.key.key) > 0 && | ||
| strcmp((char *)backhaul_vap_info->u.bss_info.security.u.key.key, INVALID_KEY) != 0) { | ||
| memset(p_tgt_vap_map->vap_array[0].u.bss_info.multi_ap_backhaul_ssid, 0, | ||
| sizeof(p_tgt_vap_map->vap_array[0].u.bss_info.multi_ap_backhaul_ssid)); | ||
| strncpy((char *)p_tgt_vap_map->vap_array[0].u.bss_info.multi_ap_backhaul_ssid, | ||
| (char *)backhaul_vap_info->u.bss_info.ssid, | ||
| sizeof(p_tgt_vap_map->vap_array[0].u.bss_info.multi_ap_backhaul_ssid) - 1); | ||
|
|
||
| memset(p_tgt_vap_map->vap_array[0].u.bss_info.multi_ap_backhaul_network_key, 0, | ||
| sizeof(p_tgt_vap_map->vap_array[0].u.bss_info.multi_ap_backhaul_network_key)); | ||
| strncpy((char *)p_tgt_vap_map->vap_array[0].u.bss_info.multi_ap_backhaul_network_key, | ||
| (char *)backhaul_vap_info->u.bss_info.security.u.key.key, | ||
| sizeof(p_tgt_vap_map->vap_array[0].u.bss_info.multi_ap_backhaul_network_key) - 1); | ||
|
|
||
| wifi_util_info_print(WIFI_CTRL, "%s:%d Copied mesh backhaul credentials to multi_ap_backhaul for private VAP %d\n", | ||
| __FUNCTION__, __LINE__, map->vap_array[i].vap_index); | ||
| } else { | ||
| wifi_util_dbg_print(WIFI_CTRL, "%s:%d Mesh backhaul credentials not found or invalid, WPS enabled without backhaul for VAP %d\n", | ||
| __FUNCTION__, __LINE__, map->vap_array[i].vap_index); | ||
| } | ||
| } |
| { | ||
| wifi_util_info_print(WIFI_CTRL, "%s:%d Vap_name: %s Mesh status: %d vap_mode: %d valid_bh: %d\n", __FUNCTION__, __LINE__, | ||
| vap_map->vap_array[j].vap_name, vap_svc_is_mesh_ext(vap_map->vap_array[j].vap_index), vap_map->vap_array[j].vap_mode, | ||
| vap_map->vap_array[j].u.sta_info.valid_bh_credentials); | ||
| if (vap_svc_is_mesh_ext(vap_map->vap_array[j].vap_index) == true && | ||
| vap_map->vap_array[j].vap_mode == wifi_vap_mode_sta && | ||
| vap_map->vap_array[j].u.sta_info.valid_bh_credentials == FALSE) | ||
| { |
| /* Only handle WPS_EV_SUCCESS (value 2) */ | ||
| if (event != 2) { | ||
| wifi_util_dbg_print(WIFI_CTRL, "%s:%d: Ignoring non-success WPS event %d\n", | ||
| __func__, __LINE__, event); | ||
| return; | ||
| } |
| int cmp_ssid_ne_vap = (strcmp(cfg.u.sta_info.ssid, vap_name) != 0); | ||
| int cmp_key_ne_invalid = (strcmp((char *)cfg.u.sta_info.security.u.key.key, INVALID_KEY) != 0); |
There was a problem hiding this comment.
| int cmp_ssid_ne_vap = (strcmp(cfg.u.sta_info.ssid, vap_name) != 0); | |
| int cmp_key_ne_invalid = (strcmp((char *)cfg.u.sta_info.security.u.key.key, INVALID_KEY) != 0); | |
| bool cmp_ssid_ne_vap = (strcmp(cfg.u.sta_info.ssid, vap_name) != 0); | |
| bool cmp_key_ne_invalid = (strcmp((char *)cfg.u.sta_info.security.u.key.key, INVALID_KEY) != 0); |
| return FALSE; | ||
| } | ||
|
|
||
| #if !defined(UWM_EXT_WPS_SUPPORT) |
There was a problem hiding this comment.
| #if !defined(UWM_EXT_WPS_SUPPORT) | |
| #ifndef UWM_EXT_WPS_SUPPORT |
| return FALSE; | ||
| } | ||
|
|
||
| #if !defined(UWM_EXT_WPS_SUPPORT) |
There was a problem hiding this comment.
| #if !defined(UWM_EXT_WPS_SUPPORT) | |
| #ifndef UWM_EXT_WPS_SUPPORT |
|
|
||
| DM_CHECK_NULL_WITH_RC(p_dm_vap_default, false); | ||
|
|
||
| #if !defined(UWM_EXT_WPS_SUPPORT) |
There was a problem hiding this comment.
| #if !defined(UWM_EXT_WPS_SUPPORT) | |
| #ifndef UWM_EXT_WPS_SUPPORT |
| return false; | ||
| } | ||
|
|
||
| #if !defined(UWM_EXT_WPS_SUPPORT) |
There was a problem hiding this comment.
| #if !defined(UWM_EXT_WPS_SUPPORT) | |
| #ifndef UWM_EXT_WPS_SUPPORT |
| wifi_vap_info_t *pcfg = (wifi_vap_info_t *)obj_ins_context; | ||
| DM_CHECK_NULL_WITH_RC(pcfg, false); | ||
|
|
||
| #if !defined(UWM_EXT_WPS_SUPPORT) |
There was a problem hiding this comment.
| #if !defined(UWM_EXT_WPS_SUPPORT) | |
| #ifndef UWM_EXT_WPS_SUPPORT |
| wifi_vap_info_t *pcfg = (wifi_vap_info_t *)obj_ins_context; | ||
| DM_CHECK_NULL_WITH_RC(pcfg, false); | ||
|
|
||
| #if !defined(UWM_EXT_WPS_SUPPORT) |
There was a problem hiding this comment.
| #if !defined(UWM_EXT_WPS_SUPPORT) | |
| #ifndef UWM_EXT_WPS_SUPPORT |
| return false; | ||
| } | ||
|
|
||
| #if !defined(UWM_EXT_WPS_SUPPORT) |
There was a problem hiding this comment.
| #if !defined(UWM_EXT_WPS_SUPPORT) | |
| #ifndef UWM_EXT_WPS_SUPPORT |
Currently we have a limitation when the WPS is enabled on 2.4G and 5G private_ssid vaps from EM onboarding, but while doing this, DataElements.Network.Topology output is breaking. This is used by EM controller for taking steering decisions.
So, as a workaround, added code to disable MLO on fronthaul/private ssid vaps when WPS onboarding is enabled in code. This is protected by macro 'EM_WPS_FH_HACK' and 'PLATFORM_BANANAPI_R4'. So the change takes into effect only on bananapi platforms when WPS easymesh onboarding is enabled.